home *** CD-ROM | disk | FTP | other *** search
/ FM Towns: Free Software Collection 8 / FM Towns Free Software Collection 8.iso / t_os / pao / etc / cdir / src / cdir.c next >
Text File  |  1994-06-01  |  22KB  |  717 lines

  1. /* << MSC V5.1 >> [FM-TOWNS] ************************************************
  2. *
  3. *    カレントディレクトリ情報取得(MS-DOS汎用)
  4. *    ----------------------------------------------------------------------
  5. *    All Rights Reserved, Copyright (C) Y.Hirata 1993.
  6. *    Programmed by Y.Hirata ( NIFTY-ID: NAB03321  パオパオ )
  7. *
  8. *    NOTE: TAB=4
  9. ****************************************************************************/
  10.  
  11. #include <stdio.h>            /*  printf,putchar    */
  12. #include <stdlib.h>            /*  exit        */
  13. #include <string.h>            /*  str*        */
  14. #include <direct.h>            /*  getcwd        */
  15. #include <conio.h>            /*  getch        */
  16.  
  17. #include "lib\define.h"        /*  定数宣言    */
  18. #include "lib\typedef.h"    /*  型宣言        */
  19. #include "lib\mem.h"        /*  _peek        */
  20. #include "lib\dirlib.h"        /*  <dos.h>,_aread    */
  21. #include "lib\doscall.h"    /*  <dos.h>,_getDPB    */
  22.  
  23. #define    isroot(s)            ((s)[1]==':' && (s)[2]=='\\' && (s)[3]=='\0')
  24.  
  25. _DPB    _dpb ;                                    /*  DPB情報                */
  26. int        FATbit ;                                /*  FATビットサイズ            */
  27.  
  28. typedef struct {
  29.     BYTE    name[8] ;        /*  ファイル名            */
  30.     BYTE    ext[3] ;        /*  拡張子            */
  31.     BYTE    attr ;            /*  属性            */
  32.     BYTE    res[10] ;        /*  リザーブ            */
  33.     WORD    time ;            /*  作成時刻        */
  34.     WORD    date ;            /*  作成日付        */
  35.     WORD    entry ;            /*  FATエントリ            */
  36.     DWORD    size ;            /*  ファイルサイズ        */
  37. } DIR_ENTRY ;
  38.  
  39. #define    ENTRYSIZE            (sizeof( DIR_ENTRY ))
  40. #define    FATBUFSIZE            8192                /*  FAT用領域サイズ        */
  41. #define    FATSECTOR            (FATBUFSIZE / _dpb.bps)
  42.  
  43. #define    ROOTSCT                (_dpb.rde * ENTRYSIZE / _dpb.bps)
  44. #define    DIRENTpS            (_dpb.bps / ENTRYSIZE)
  45. #define    DIRENTpC            (DIRENTpS * (_dpb.spc+1))
  46.  
  47. unsigned    _cdrv ;                                /*  カレントドライブ            */
  48. char        *_cdir ;                            /*  カレントディレクトリ            */
  49. char        _abspath[128] ;                        /*  物理パス名            */
  50. BYTE        *_fat ;                                /*  FATテーブル領域        */
  51. DWORD        _fatss ;                            /*  開始セクタ番号            */
  52. DIR_ENTRY    *_direntry ;                        /*  ディレクトリエントリ            */
  53. WORD        _maxentry ;                            /*  最大FATエントリ            */
  54. WORD        _nentry ;                            /*  有効エントリ数            */
  55. WORD        _dentry ;                            /*  削除エントリ数            */
  56.  
  57. #define    LINEpPAGE            24                    /*  1画面の行数            */
  58. int            _linecnt ;                            /*  表示行数            */
  59.  
  60. struct {
  61.     unsigned    critical:1 ;    /*  致命的エラー発生フラグ    */
  62.     unsigned    rootdir:1 ;        /*  ルートディレクトリ識別フラグ    */
  63.     unsigned    fat:1 ;            /*  FAT読み込み済フラグ    */
  64.     unsigned    sct32:1 ;        /*  32bitセクタサポートフラグ    */
  65. } _flg ;                                        /*  処理フラグ            */
  66.  
  67. struct {
  68.     unsigned    color:1 ;    /*  色付表示                */
  69.     unsigned    dinf:1 ;    /*  ドライブ情報表示            */
  70.     unsigned    sector:1 ;    /*  ディレクトリエントリのセクタ表示    */
  71.     unsigned    page:1 ;    /*  ページ制御                */
  72. } _optsw ;                                        /*  オプションスイッチ            */
  73.  
  74. void putcrlf( void )
  75. /*===========================================================================
  76. *    改行表示
  77. ===========================================================================*/
  78. {
  79.     putchar( '\n' ) ;
  80.     if ( !_optsw.page ) return ;
  81.     if ( ++_linecnt > LINEpPAGE-2 ) {
  82.         printf( "--- more ---" ) ;
  83.         getch() ;
  84.         putchar( '\n' ) ;
  85.         _linecnt=0 ;
  86.     }
  87. }
  88.  
  89. void getDPB( void )
  90. /*===========================================================================
  91. *    DPB情報取得
  92. ===========================================================================*/
  93. {
  94.     WORD    attr ;
  95.  
  96.     _getDPB( _cdrv,&_dpb ) ;
  97.     if ( _dpb.maxclst < 0x0FF7 ) {
  98.         FATbit  = 12 ;                            /*  12bit FAT        */
  99.         _maxentry = 0x0FF7 ;
  100.     } else {
  101.         FATbit  = 16 ;                            /*  16bit FAT        */
  102.         _maxentry = 0xFFF7 ;
  103.     }
  104.     if ( _osmajor >= 10 ) {                        /*  OS/2互換BOX        */
  105.         _flg.sct32 = 1 ;
  106.         return ;
  107.     }
  108.     attr = (WORD)_peek( _dpb.dseg,_dpb.doff+4 ) ;
  109.     _flg.sct32 = ( attr & 0x0002 ) ? 1 : 0 ;    /*  32bitセクタサポート?    */
  110. }
  111.  
  112. int absRead( WORD nsct,DWORD sctno,void *buf )
  113. /*===========================================================================
  114. *    物理読み込み
  115. *    < IN  >    : nsct    読み込みセクタ数
  116. *            : sctno    読み込み開始セクタ番号
  117. *            : buf    データ格納先アドレス
  118. *    < OUT >    : buf    読み込んだデータ
  119. *    < RET >    : 下位バイトにエラーコードを返す. (上位バイト=00h:正常終了, =01h:エラー発生)
  120. *                =00h    書き込み禁止である
  121. *                =01h    ユニットが存在しない
  122. *                =02h    ドライブの準備ができていない
  123. *                =03h    存在しないコマンドである
  124. *                =04h    データのCRCエラー
  125. *                =05h    バッドドライブリクエストストラクチャの長さ
  126. *                =06h    シークエラー
  127. *                =07h    存在しないメディアタイプである
  128. *                =08h    セクタが存在しない
  129. *                =09h    プリンタの用紙切れ
  130. *                =0Ah    書き込み不良
  131. *                =0Bh    読み込み不良
  132. *                =0Ch    一般的なディスク不良
  133. *                =0Fh    不正なメディア交換があった
  134. ===========================================================================*/
  135. {
  136.     struct {
  137.         DWORD    sctno ;                            /*  32bitセクタ番号        */
  138.         WORD    nsct ;                            /*  R/Wセクタ数            */
  139.         WORD    off ;                            /*  バッファオフセット            */
  140.         WORD    seg ;                            /*  バッファセグメント            */
  141.     } packet ;
  142.  
  143.     if ( _flg.sct32 ) {                            /*  32bitセクタサポート        */
  144.         packet.sctno = sctno ;
  145.         packet.nsct  = nsct ;
  146.         packet.off   = _off( buf ) ;
  147.         packet.seg   = _seg( buf ) ;
  148.         return _aread( _cdrv-1,-1,-1,&packet ) ;
  149.     }
  150.     return _aread( _cdrv-1,nsct,(WORD)sctno,buf ) ;
  151. }
  152.  
  153. DWORD tosector( WORD cluster )
  154. /*===========================================================================
  155. *    クラスタ値→論理セクタ番号 (サブディレクトリ時)
  156. ===========================================================================*/
  157. {
  158.     DWORD    sector ;
  159.  
  160.     cluster -= 2 ;
  161.     sector = (DWORD)cluster ;
  162.     sector <<= _dpb.scnt ;
  163.     sector += (DWORD)_dpb.fds ;
  164.     return sector ;
  165. }
  166.  
  167. int fatRead( DWORD *off )
  168. /*===========================================================================
  169. *    FAT読み込み済かどうかのチェック
  170. *    < RET >    : エラコードを返す.
  171. *                =0    正常終了
  172. *                =1    セクタ読み込み失敗
  173. ===========================================================================*/
  174. {
  175.     DWORD    sp, ep, fsector ;
  176.     int        ret ;
  177.  
  178.     sp = _fatss * (DWORD)_dpb.bps ;
  179.     ep = (DWORD)( FATSECTOR * _dpb.bps ) ;        /*  FATバッファサイズ        */
  180.     ep = sp + ep - 2L ;                            /*  WORD読み込みのため    */
  181.     if ( *off < sp || *off > ep || !_flg.fat ) {    /*  FAT読み込み        */
  182.         _fatss  = *off / (DWORD)_dpb.bps ;
  183.         fsector = (DWORD)_dpb.res + _fatss ;
  184.         ret = absRead( FATSECTOR,fsector,_fat ) ;
  185.         if ( ret ) {
  186.             printf( "\aFATの読み込みに失敗しました." ) ;
  187.             printf( " (セクタNo.%08lX~%uセクタ分, error code: %02Xh)",
  188.                                             fsector,FATSECTOR,_lo(ret) ) ;
  189.             putcrlf() ;
  190.             return 1 ;
  191.         }
  192.         sp = _fatss * (DWORD)_dpb.bps ;
  193.         _flg.fat = 1 ;
  194.     }
  195.     *off -= sp ;                                /*  現バッファ中のオフセット    */
  196.     return 0 ;
  197. }
  198.  
  199. int nextcluster( WORD *cluster )
  200. /*===========================================================================
  201. *    次のクラスタ取得
  202. *    < RET >    : エラコードを返す.
  203. *                =0    正常終了
  204. *                =1    セクタ読み込み失敗
  205. ===========================================================================*/
  206. {
  207.     WORD    next, clst ;
  208.     DWORD    nextp ;
  209.  
  210.     clst = *cluster ;
  211.     if ( FATbit == 12 ) {                        /*  12bit FAT            */
  212.         nextp = (DWORD)clst + (DWORD)( clst >> 1 ) ;        /*  ×1.5    */
  213.         if ( fatRead( &nextp ) ) return 1 ;
  214.         next = (WORD)nextp ;
  215.         next = _WORD( _fat + next ) ;
  216.         clst = ( clst & 1 ? ( next >> 4 ) : ( next & 0x0FFF ) ) ;
  217.     } else {                                    /*  16bit FAT            */
  218.         nextp = (DWORD)clst + (DWORD)clst ;                    /*  ×2        */
  219.         if ( fatRead( &nextp ) ) return 1 ;
  220.         next = (WORD)nextp ;
  221.         clst = _WORD( _fat + next ) ;
  222.     }
  223.     *cluster = clst ;
  224.     return 0 ;
  225. }
  226.  
  227. void dispColor( int entry )
  228. /*===========================================================================
  229. *    表示色設定
  230. ===========================================================================*/
  231. {
  232.     if ( _direntry[entry].name[0] == 0x00 )                /*  空き        */
  233.         return ;
  234.     else if ( _direntry[entry].name[0] == 0xE5 )        /*  削除        */
  235.         printf( "\x1b[31m" ) ;
  236.     else if ( _direntry[entry].name[0] == 0x2E )        /*  サブディレクトリ    */
  237.         printf( "\x1b[36m" ) ;
  238.     else if ( _direntry[entry].attr & _A_SUBDIR )        /*  サブディレクトリ    */
  239.         printf( "\x1b[36m" ) ;
  240.     else if ( _direntry[entry].attr & _A_VOLID )        /*  ボリュームラベル    */
  241.         printf( "\x1b[33m" ) ;
  242.     else if ( _direntry[entry].attr & _A_SYSTEM )        /*  システム        */
  243.         printf( "\x1b[32m" ) ;
  244.     else if ( _direntry[entry].attr & _A_HIDDEN )        /*  隠し        */
  245.         printf( "\x1b[32m" ) ;
  246.     else if ( _direntry[entry].attr & _A_RDONLY )        /*  書込禁止    */
  247.         printf( "\x1b[32m" ) ;
  248. }
  249.  
  250. int dispFname( int entry )
  251. /*===========================================================================
  252. *    ファイル名表示
  253. ===========================================================================*/
  254. {
  255.     register int    cnt ;
  256.  
  257.     if ( _direntry[entry].name[0] == 0x00 ) return 1 ;    /*  空きエントリ    */
  258.     if ( _direntry[entry].name[0] == 0x05 ) {            /*  1byte目がE5    */
  259.         _nentry++ ;
  260.         putchar( 0xE5 ) ;
  261.     } else if ( _direntry[entry].name[0] == 0xE5 ) {    /*  削除エントリ    */
  262.         _dentry++ ;
  263.         putchar( '?' ) ;
  264.     } else {                                            /*  通常エントリ    */
  265.         _nentry++ ;
  266.         putchar( _direntry[entry].name[0] ) ;
  267.     }
  268.     for ( cnt=1; cnt<8; cnt++ )
  269.         putchar( _direntry[entry].name[cnt] ) ;            /*  ファイル名        */
  270.     putchar( ' ' ) ;
  271.     for ( cnt=0; cnt<3; cnt++ )
  272.         putchar( _direntry[entry].ext[cnt] ) ;            /*  拡張子        */
  273.     return 0 ;
  274. }
  275.  
  276. void dispFattr( BYTE attr )
  277. /*===========================================================================
  278. *    ファイル属性表示
  279. ===========================================================================*/
  280. {
  281.     putchar( attr & _A_ARCH   ? 'a' : '-' ) ;
  282.     putchar( attr & _A_SYSTEM ? 's' : '-' ) ;
  283.     putchar( attr & _A_HIDDEN ? 'h' : '-' ) ;
  284.     putchar( attr & _A_RDONLY ? 'o' : 'w' ) ;
  285. }
  286.  
  287. void dispEntry( void )
  288. /*===========================================================================
  289. *    カレントディレクトリエントリ情報表示
  290. ===========================================================================*/
  291. {
  292.     register int    entry ;
  293.  
  294.     for ( entry=0; entry<DIRENTpS; entry++ ) {
  295.         if ( _optsw.color ) dispColor( entry ) ;
  296.         if ( dispFname( entry ) ) continue ;
  297.         if ( _direntry[entry].attr & _A_VOLID )
  298.             printf( "  < VOL >" ) ;
  299.         else if ( _direntry[entry].attr & _A_SUBDIR )
  300.             printf( "  < DIR >" ) ;
  301.         else
  302.             printf( " %8ld",_direntry[entry].size ) ;
  303.         printf( "  %02d-%02d-%02d  %2d:%02d:%02d  ",
  304.             YEAR(_direntry[entry].date),MONTH(_direntry[entry].date),
  305.             DATE(_direntry[entry].date),HOUR(_direntry[entry].time),
  306.             MINUTE(_direntry[entry].time),SEC(_direntry[entry].time) ) ;
  307.         dispFattr( _direntry[entry].attr ) ;
  308.         printf( "  (cluster=%04X",_direntry[entry].entry ) ;
  309.         if ( _direntry[entry].entry < 1 ) {
  310.             ;
  311.         } else if ( _direntry[entry].entry < _maxentry ) {
  312.             printf( ":sector=%08lX",tosector( _direntry[entry].entry ) ) ;
  313.         } else if ( _direntry[entry].entry == _maxentry ) {
  314.             printf( ":不良クラスタ" ) ;
  315.         } else {
  316.             printf( ":最終クラスタ" ) ;
  317.         }
  318.         printf( _optsw.color ? ")\x1b[m" : ")" ) ;
  319.         putcrlf() ;
  320.     }
  321. }
  322.  
  323. int dispCdir( void )
  324. /*===========================================================================
  325. *    カレントディレクトリエントリ表示
  326. *    < RET >    : エラコードを返す.
  327. *                =0    正常終了
  328. *                =1    セクタ読み込み失敗
  329. *                =2    ファイルが見つからない
  330. ===========================================================================*/
  331. {
  332.     register WORD    cnt ;
  333.     struct find_t    dta ;
  334.     unsigned    attr=(_A_RDONLY|_A_HIDDEN|_A_SYSTEM|_A_SUBDIR|_A_ARCH) ;
  335.     WORD    cluster ;
  336.     DWORD    sector ;
  337.     int        ret ;
  338.  
  339.     if ( _dos_findfirst( "*.*",attr,&dta ) && !_flg.rootdir ) return 2 ;
  340. /*
  341. *    最初の検索時に, ルートディレクトリでなければ '.' が見つかる筈である.
  342. *    カレントディレクトリのエントリは, '.' の指しているクラスタをディレクトリエントリとして処理する.
  343. */
  344.     _nentry = _dentry = 0 ;
  345.     putcrlf() ;
  346.     if ( _flg.rootdir ) {                        /*  root directory        */
  347.         sector = (DWORD)_dpb.fsr ;
  348.         for ( cnt=0; cnt<ROOTSCT; cnt++, sector++ ) {
  349.             if ( _optsw.sector ) {
  350.                 printf( "< sector:%08lX >",sector ) ;
  351.                 putcrlf() ;
  352.             }
  353.             ret = absRead( 1,sector,_direntry ) ;
  354.             if ( ret ) {
  355.                 printf( "_aread error : %02Xh",_lo(ret) ) ;
  356.                 putcrlf() ;
  357.                 return 1 ;
  358.             }
  359.             dispEntry() ;                        /*  ディレクトリエントリ表示        */
  360.         }
  361.     } else {                                    /*  sub directory        */
  362.         cluster = _WORD( (char *)&dta + 0x0F ) ;
  363.         for ( ; cluster<_maxentry; ) {
  364.             sector = tosector( cluster ) ;
  365.             for ( cnt=0; cnt<_dpb.spc+1; cnt++, sector++ ) {
  366.                 if ( _optsw.sector ) {
  367.                     printf( "< sector:%08lX >",sector ) ;
  368.                     putcrlf() ;
  369.                 }
  370.                 ret = absRead( 1,sector,_direntry ) ;
  371.                 if ( ret ) {
  372.                     printf( "_aread error : %02Xh",_lo(ret) ) ;
  373.                     putcrlf() ;
  374.                     return 1 ;
  375.                 }
  376.                 dispEntry() ;                    /*  ディレクトリエントリ表示        */
  377.             }
  378.             if ( nextcluster( &cluster ) ) return 1 ;
  379.         }
  380.     }
  381.     putcrlf() ;
  382.     printf( "%6d 個の有効エントリがあります.",_nentry ) ;
  383.     putcrlf() ;
  384.     printf( "%6d 個の削除エントリがあります.",_dentry ) ;
  385.     putcrlf() ;
  386.     return 0 ;
  387. }
  388.  
  389. void dispLabel( void )
  390. /*===========================================================================
  391. *    ボリュームラベル表示
  392. ===========================================================================*/
  393. {
  394.     register int    cp ;
  395.     struct find_t    dta ;
  396.     unsigned    attr=_A_VOLID ;
  397.     int        findflg=0 ;
  398.  
  399.     if ( !_dos_findfirst( "\\*.*",attr,&dta ) ) {
  400.         do {
  401.             if ( dta.attrib & _A_VOLID ) findflg = 1 ;
  402.         } while ( !_dos_findnext( &dta ) ) ;    /*  次のエントリ            */
  403.     }
  404.     if ( findflg ) {
  405.         for ( cp=0; cp<12; cp++ )
  406.             if ( dta.name[cp] == '.' )
  407.                 strcpy( dta.name+cp,dta.name+cp+1 ) ;
  408.         printf( " %s",dta.name ) ;
  409.     } else {
  410.         printf( "ありません." ) ;
  411.     }
  412.     putcrlf() ;
  413. }
  414.  
  415. void dispDrvErr( void )
  416. /*===========================================================================
  417. *    ドライブ指定誤り表示
  418. ===========================================================================*/
  419. {
  420.     _flg.critical = 1 ;
  421.     printf( "\a ドライブの指定が違います." ) ;
  422.     putcrlf() ;
  423. }
  424.  
  425. int dispCurrent( void )
  426. /*===========================================================================
  427. *    カレントディレクトリ表示
  428. ===========================================================================*/
  429. {
  430.     putcrlf() ;
  431.     printf( " ドライブ %c: のディスクのボリュームラベルは",_cdrv+'@' ) ;
  432.     dispLabel() ;
  433.     if ( getabspath( _cdir,_abspath ) ) {        /*  物理パス名取得        */
  434.         dispDrvErr() ;
  435.         return 1 ;
  436.     }
  437.     printf( " ディレクトリは %s",_cdir ) ;
  438.     putcrlf() ;
  439.     if ( isnetdrv( _cdrv ) ) {                    /*  リモート                */
  440.         putcrlf() ;
  441.         printf( "\a %c: はリモートドライブ",_cdrv+'@' ) ;
  442.         printf( "(DOSによる物理アクセス不可)のため扱えません." ) ;
  443.         putcrlf() ;
  444.         return 1 ;
  445.     }
  446.     if ( isjoindrv( _cdrv ) || stricmp( _cdir,_abspath ) ) {
  447.         putcrlf() ;
  448.         printf( "\a このドライブは再割当されています." ) ;
  449.         putcrlf() ;
  450.         printf( "   物理パス名は %s",_abspath ) ;
  451.         putcrlf() ;
  452.     }
  453.     return 0 ;
  454. }
  455.  
  456. int init( void )
  457. /*===========================================================================
  458. *    初期処理
  459. *    < RET >    : エラコードを返す.
  460. *                =0    正常終了
  461. *                =1    セクタ読み込み失敗
  462. *                =2    メモリ不足(FAT領域)
  463. *                =3    メモリ不足(ディレクトリエントリ)
  464. *                =4    物理アクセス不可
  465. ===========================================================================*/
  466. {
  467.     _flg.critical = 0 ;
  468.     resetdisk() ;                                /*  リセットディスク            */
  469.     _dos_getdrive( &_cdrv ) ;                    /*  カレントドライブ            */
  470.     _cdir = getcwd( NULL,_MAX_DIR ) ;            /*  カレントディレクトリ取得        */
  471.     if ( dispCurrent() ) return 4 ;                /*  カレントディレクトリ表示        */
  472.     _flg.rootdir = isroot( _abspath ) ;            /*  ルートディレクトリ識別        */
  473.     getDPB() ;                                    /*  DPB情報取得            */
  474.     _flg.fat = 0 ;
  475.     _fat = NULL ;
  476.     _direntry = NULL ;
  477.     if ( !_flg.rootdir ) {                        /*  ルートディレクトリでない時    */
  478.         if ( (_fat = (BYTE *)malloc( FATBUFSIZE )) == NULL ) {
  479.             return 2 ;
  480.         }
  481.         _fatss = 0L ;
  482.     }
  483.     if ( (_direntry = (DIR_ENTRY *)malloc( _dpb.bps )) == NULL ) {
  484.         if ( _fat != NULL ) free( _fat ) ;
  485.         return 3 ;
  486.     }
  487.     return 0 ;
  488. }
  489.  
  490. void dispDpb( void )
  491. /*===========================================================================
  492. *    ディスク情報表示
  493. ===========================================================================*/
  494. {
  495.     putcrlf() ;
  496.     printf( "< %d bit FAT >",FATbit ) ;
  497.     if ( _flg.sct32 ) printf( " ( 32bitセクタ番号サポート )" ) ;
  498.     putcrlf() ;
  499.     printf( "bytes/sector .................. %u",_dpb.bps ) ;
  500.     putcrlf() ;
  501.     printf( "sectors/cluster ............... %u",_dpb.spc+1 ) ;
  502.     putcrlf() ;
  503.     printf( "shift count ................... %d",_dpb.scnt ) ;
  504.     putcrlf() ;
  505.     printf( "reserved sectors .............. %u",_dpb.res ) ;
  506.     putcrlf() ;
  507.     printf( "sectors/FAT ................... %u",_dpb.spf ) ;
  508.     putcrlf() ;
  509.     printf( "first data sector ............. %04Xh",_dpb.fds ) ;
  510.     putcrlf() ;
  511.     printf( "first sector of root directry . %04Xh",_dpb.fsr ) ;
  512.     putcrlf() ;
  513.     printf( "directory entries/cluster ..... %u",DIRENTpC ) ;
  514.     putcrlf() ;
  515.     printf( _flg.rootdir ? "< root " : "< sub " ) ;
  516.     printf( "directory >" ) ;
  517.     putcrlf() ;
  518. }
  519.  
  520. void dispSize( DWORD size )
  521. /*===========================================================================
  522. *    サイズ表示
  523. ===========================================================================*/
  524. {
  525.     double    sizew ;
  526.  
  527.     sizew = (double)size ;
  528.     if ( size < 1024L ) {                        /*  1024未満            */
  529.         printf( "%10ld バイト               ",size ) ;
  530.     } else if ( size < 1048576L ) {                /*  1024*1024未満        */
  531.         printf( "%10ld バイト (約 %6.1lf KB)",size,sizew/1024.0L ) ;
  532.     } else {                                    /*  1024*1024以上        */
  533.         printf( "%10ld バイト (約 %6.1lf MB)",size,sizew/1048576.0L ) ;
  534.     }
  535. }
  536.  
  537. void dispDrive( void )
  538. /*===========================================================================
  539. *    ドライブ容量表示
  540. ===========================================================================*/
  541. {
  542.     struct diskfree_t    dinf ;
  543.     DWORD    size ;
  544.     double    pers ;
  545.     int        cdrom ;
  546.  
  547.     putcrlf() ;
  548.     if ( _dos_getdiskfree( 0,&dinf ) ) {        /*  ドライブ情報取得        */
  549.         dispDrvErr() ;
  550.         return ;
  551.     }
  552.     cdrom = iscdrom( 0 ) ;
  553.  
  554.     /*    全ディスク容量
  555.     ---------------- */
  556.     if ( !cdrom ) {                                /*  通常ドライブ            */
  557.         size = (DWORD)dinf.total_clusters
  558.              * (DWORD)dinf.sectors_per_cluster
  559.              * (DWORD)dinf.bytes_per_sector ;
  560.     } else {                                    /*  CD-ROM                */
  561.         size = 270000L
  562.              * (DWORD)dinf.sectors_per_cluster
  563.              * (DWORD)dinf.bytes_per_sector ;
  564.     }
  565.     printf( " 全ディスク容量   : " ) ;
  566.     dispSize( size ) ;
  567.     putcrlf() ;
  568.  
  569.     /*    使用ディスク容量
  570.     ------------------ */
  571.     if ( !cdrom ) {                                /*  通常ドライブ            */
  572.         size = (DWORD)( dinf.total_clusters - dinf.avail_clusters )
  573.              * (DWORD)dinf.sectors_per_cluster
  574.              * (DWORD)dinf.bytes_per_sector ;
  575.         printf( " 使用ディスク容量 : " ) ;
  576.         dispSize( size ) ;
  577.         putcrlf() ;
  578.     }
  579.  
  580.     /*    残りディスク容量
  581.     ------------------ */
  582.     size = (DWORD)dinf.avail_clusters
  583.          * (DWORD)dinf.sectors_per_cluster
  584.          * (DWORD)dinf.bytes_per_sector ;
  585.     if ( _optsw.color ) printf( "\x1b[33m" ) ;
  586.     printf( " 残りディスク容量 : " ) ;
  587.     dispSize( size ) ;
  588.  
  589.     /*    使用率
  590.     ----------- */
  591.     pers = (double)dinf.avail_clusters / (double)dinf.total_clusters ;
  592.     pers = ( 1.0L - pers ) * 100.0L ;
  593.     if ( !cdrom ) {                                /*  通常ドライブ            */
  594.         printf( "  ディスク使用率(%5.1lf %%)",pers ) ;
  595.         if ( _optsw.color ) printf( "\x1b[m" ) ;
  596.         putcrlf() ;
  597.     } else {                                    /*  CD-ROM                */
  598.         printf( "  < CD-ROM >" ) ;
  599.         if ( _optsw.color ) printf( "\x1b[m" ) ;
  600.         putcrlf() ;
  601.     }
  602.  
  603.     /*    クラスタサイズ
  604.     ------------- */
  605.     size = (DWORD)dinf.sectors_per_cluster * (DWORD)dinf.bytes_per_sector ;
  606.     printf( " クラスタサイズ   : " ) ;
  607.     dispSize( size ) ;
  608.     putcrlf() ;
  609. }
  610.  
  611. void usage( void )
  612. /*===========================================================================
  613. *    使用方法表示
  614. ===========================================================================*/
  615. {
  616.     printf( "カレントディレクトリ情報表示 (C) パオパオ 1993.\n\n" ) ;
  617.     printf( "Usage: cdir [-c] [-i] [-s] [-p]\n" ) ;
  618.     printf( "       -c   色付表示\n" ) ;
  619.     printf( "       -i   ドライブ情報表示\n" ) ;
  620.     printf( "       -s   読み込みセクタ番号表示\n" ) ;
  621.     printf( "       -p   1画面毎表示\n" ) ;
  622.     exit( 1 ) ;
  623. }
  624.  
  625. void swchk( char *str )
  626. /*===========================================================================
  627. *    オプションスイッチ評価
  628. ===========================================================================*/
  629. {
  630.     register int    cnt ;
  631.  
  632.     for ( cnt=0; cnt<strlen(str); cnt++ ) {
  633.         if ( str[cnt] == '-' || str[cnt] == '/' ) continue ;
  634.         switch ( str[cnt] ) {
  635.         case 'c'    :
  636.         case 'C'    :
  637.             _optsw.color = TRUE ;    break ;
  638.         case 'i'    :
  639.         case 'I'    :
  640.             _optsw.dinf = TRUE ;    break ;
  641.         case 's'    :
  642.         case 'S'    :
  643.             _optsw.sector = TRUE ;    break ;
  644.         case 'p'    :
  645.         case 'P'    :
  646.             _optsw.page = TRUE ;    break ;
  647.         default        :
  648.             usage() ;
  649.         }
  650.     }
  651. }
  652.  
  653. void clroption( void )
  654. /*===========================================================================
  655. *    オプションスイッチクリア
  656. ===========================================================================*/
  657. {
  658.     _optsw.color  = 0 ;
  659.     _optsw.dinf   = 0 ;
  660.     _optsw.sector = 0 ;
  661.     _optsw.page   = 0 ;
  662.  
  663.     _linecnt      = 0 ;
  664. }
  665.  
  666. void clrdata( void )
  667. /*===========================================================================
  668. *    データクリア
  669. ===========================================================================*/
  670. {
  671.     if ( _direntry != NULL ) free( _direntry ) ;
  672.     if ( _fat != NULL ) free( _fat ) ;
  673. }
  674.  
  675. int main( int ac,char *av[] )
  676. /*===========================================================================
  677. *    メイン
  678. ===========================================================================*/
  679. {
  680.     int        ret, cnt ;
  681.  
  682.     clroption() ;                                /*  オプションスイッチ/フラグクリア    */
  683.     if ( ac > 1 ) {                                /*  引数あり            */
  684.         for ( cnt=1; cnt<ac; cnt++ ) {
  685.             if ( *av[cnt] == '-' || *av[cnt] == '/' )
  686.                 swchk( av[cnt]+1 ) ;            /*  引数チェック            */
  687.             else
  688.                 usage() ;                        /*  使用方法表示        */
  689.         }
  690.     }
  691.     ret = init() ;                                /*  初期処理            */
  692.     if ( _optsw.dinf && ret != 4 ) dispDpb() ;    /*  ディスク情報表示        */
  693.     switch ( ret ) {
  694.     case 2    :
  695.         printf( "\aFAT用の領域が確保できませんでした." ) ;
  696.         putcrlf() ;
  697.         break ;
  698.     case 3    :
  699.         printf( "\aディレクトリエントリ用の領域が確保できませんでした." ) ;
  700.         putcrlf() ;
  701.         break ;
  702.     }
  703.     if ( !ret ) {
  704.         if ( dispCdir() == 2 ) {                /*  カレントディレクトリ情報表示    */
  705.             printf( "ファイルが見つかりません." ) ;
  706.             putcrlf() ;
  707.         }
  708.     }
  709.     if ( _optsw.dinf && !_flg.critical )
  710.         dispDrive() ;                            /*  ドライブ容量表示        */
  711.     clrdata() ;                                    /*  データクリア                */
  712.     resetdisk() ;                                /*  リセットディスク            */
  713.  
  714.     return 0 ;
  715. }
  716.  
  717.